import * as THREE from 'three';
import { useEffect, useRef } from 'react';

function ParticleAnimation() {
  const mountRef = useRef(null);

  useEffect(() => {
    // Scene setup
    const scene = new THREE.Scene();
    const camera = new THREE.PerspectiveCamera(75, window.innerWidth / window.innerHeight, 0.1, 1000);
    const renderer = new THREE.WebGLRenderer({ antialias: true });
    renderer.setSize(window.innerWidth, window.innerHeight);
    renderer.setClearColor(0x000000); // Black background
    mountRef.current.appendChild(renderer.domElement);

    // Main particles (symmetric blue-purple cloud)
    const particleCount = 20000; // Higher density for detail
    const positions = new Float32Array(particleCount * 3);
    const colors = new Float32Array(particleCount * 3);

    for (let i = 0; i < particleCount; i++) {
      const angle = Math.random() * Math.PI * 2; // For symmetric distribution
      const radius = Math.random() * 10 + 5; // Base radius for cloud size
      const x = Math.cos(angle) * radius * (1 + Math.sin(angle * 3) * 0.3); // Horizontal waves with branches
      const y = Math.sin(angle) * 2 + Math.sin(x * 0.5) * 1.5 + (Math.random() - 0.5) * 1; // Vertical variation
      const z = (Math.random() - 0.5) * 3 + Math.cos(x * 0.4) * 1; // Depth for 3D feel

      positions[i * 3] = x;
      positions[i * 3 + 1] = y;
      positions[i * 3 + 2] = z;

      // Uniform blue-purple colors with slight variation
      const hueVariation = Math.random() * 0.1 + 0.7;
      colors[i * 3] = hueVariation * 0.2; // R low
      colors[i * 3 + 1] = hueVariation * 0.3; // G low
      colors[i * 3 + 2] = hueVariation; // B high
    }

    const geometry = new THREE.BufferGeometry();
    geometry.setAttribute('position', new THREE.BufferAttribute(positions, 3));
    geometry.setAttribute('color', new THREE.BufferAttribute(colors, 3));

    const material = new THREE.PointsMaterial({
      size: 0.02, // Finer particles
      vertexColors: true,
      transparent: true,
      opacity: 0.6,
      blending: THREE.AdditiveBlending, // Glow effect
    });

    const particles = new THREE.Points(geometry, material);
    scene.add(particles);

    // Central white smoke/lightning particles (vertical and elongated)
    const smokeCount = 1500; // Higher density for thickness
    const smokePositions = new Float32Array(smokeCount * 3);
    const smokeColors = new Float32Array(smokeCount * 3);

    for (let i = 0; i < smokeCount; i++) {
      const t = i / smokeCount; // Parameter from bottom to top
      const x = Math.sin(t * Math.PI * 6) * 0.5 + (Math.random() - 0.5) * 0.2; // Slight wavy lightning
      const y = (t * 10) - 5 + Math.cos(t * Math.PI * 2) * 0.5; // Vertical elongation with curve
      const z = Math.cos(t * Math.PI * 6) * 0.3 + (Math.random() - 0.5) * 0.1;

      smokePositions[i * 3] = x;
      smokePositions[i * 3 + 1] = y;
      smokePositions[i * 3 + 2] = z;

      // White colors with fade at ends
      const intensity = 1 - Math.abs(t - 0.5) * 0.5; // Brighter in center
      smokeColors[i * 3] = intensity;
      smokeColors[i * 3 + 1] = intensity;
      smokeColors[i * 3 + 2] = intensity * 0.95 + 0.05; // Very slight blue
    }

    const smokeGeometry = new THREE.BufferGeometry();
    smokeGeometry.setAttribute('position', new THREE.BufferAttribute(smokePositions, 3));
    smokeGeometry.setAttribute('color', new THREE.BufferAttribute(smokeColors, 3));

    const smokeMaterial = new THREE.PointsMaterial({
      size: 0.05,
      vertexColors: true,
      transparent: true,
      opacity: 0.8,
      blending: THREE.AdditiveBlending,
    });

    const smokeParticles = new THREE.Points(smokeGeometry, smokeMaterial);
    scene.add(smokeParticles);

    // Camera position
    camera.position.set(0, 0, 18); // Adjusted for compact view
    camera.lookAt(0, 0, 0);

    // Animation loop
    let time = 0;
    const animate = () => {
      requestAnimationFrame(animate);

      time += 0.003; // Even slower for subtle animation

      // Animate main particles (pulsing and wave flow)
      particles.rotation.y += 0.0001; // Very slow rotation
      particles.scale.set(1 + Math.sin(time) * 0.01, 1 + Math.sin(time) * 0.01, 1); // Gentle pulsing
      const posAttr = particles.geometry.getAttribute('position');
      for (let i = 0; i < particleCount; i++) {
        const origX = positions[i * 3];
        const origY = positions[i * 3 + 1];
        const origZ = positions[i * 3 + 2];
        posAttr.array[i * 3] = origX + Math.sin(time + origY * 0.1) * 0.01; // Subtle horizontal flow
        posAttr.array[i * 3 + 1] = origY + Math.cos(time + origX * 0.1) * 0.02; // Vertical wave
        posAttr.array[i * 3 + 2] = origZ + Math.sin(time + origZ * 0.1) * 0.005; // Depth variation
      }
      posAttr.needsUpdate = true;

      // Animate smoke (upward drift with twist)
      const smokePosAttr = smokeParticles.geometry.getAttribute('position');
      for (let i = 0; i < smokeCount; i++) {
        smokePosAttr.array[i * 3 + 1] += 0.002; // Slow upward
        smokePosAttr.array[i * 3] += Math.sin(time + i * 0.01) * 0.001; // Gentle twist
        if (smokePosAttr.array[i * 3 + 1] > 5) {
          smokePosAttr.array[i * 3 + 1] = -5 + (Math.random() - 0.5) * 0.5; // Reset to bottom
        }
      }
      smokePosAttr.needsUpdate = true;

      renderer.render(scene, camera);
    };

    animate();

    // Handle resize
    const handleResize = () => {
      camera.aspect = window.innerWidth / window.innerHeight;
      camera.updateProjectionMatrix();
      renderer.setSize(window.innerWidth, window.innerHeight);
    };
    window.addEventListener('resize', handleResize);

    // Cleanup
    return () => {
      window.removeEventListener('resize', handleResize);
      mountRef.current?.removeChild(renderer.domElement);
    };
  }, []);

  return <div ref={mountRef} style={{ width: '100%', height: '100%' }} />;
}

export default ParticleAnimation;